package secondweek.four;

import org.junit.Test;
import org.nutz.lang.Encoding;
import org.nutz.lang.Files;
import org.nutz.lang.Lang;
import org.nutz.lang.Times;

import java.io.File;
import java.io.FileWriter;
import java.io.IOException;
import java.util.*;
import java.util.concurrent.ExecutionException;
import java.util.concurrent.ForkJoinPool;
import java.util.concurrent.Future;

/**
 * Created by zhourui on 2016/8/11.
 * 随机生成 Salary {name, baseSalary, bonus  }的记录，如“wxxx,10,1”，每行一条记录，总共1000万记录，写入文本文件（UFT-8编码），
 然后读取文件，name的前两个字符相同的，其年薪累加，比如wx，100万，3个人，最后做排序和分组，输出年薪总额最高的10组：
 wx, 200万，10人
 lt, 180万，8人
 ....
 */
public class SaveAndSortSalary4 {

    @Test
    public void test(){
        File file = new File("D:\\aaa.txt");
        try {
            file.createNewFile();
        } catch (IOException e) {
            e.printStackTrace();
        }

        //生成数据，写入文件
        Date timeBegin = Times.now();

        writeFileUseFileWriter(file);

        Date afterWriteFile = Times.now();
        System.out.println("write file:" + (afterWriteFile.getTime()-timeBegin.getTime()) + "ms");

        //读取文件，排序
        List<String> salaries = readFile(file);

        Date afterReadFile = Times.now();
        System.out.println("read file:" + (afterReadFile.getTime()-afterWriteFile.getTime()) + "ms");

        Collections.sort(salaries, new Comparator<String>() {
            public int compare(String o1, String o2) {
                if (o1.charAt(0) > o2.charAt(0)){
                    return 1;
                } else if (o1.charAt(0) == o2.charAt(0)){
                    if (o1.charAt(1) > o2.charAt(1)){
                        return 1;
                    }else if (o1.charAt(1) == o2.charAt(1)){
                        return 0;
                    }else{
                        return -1;
                    }
                }
                return -1;
            }
        });

        //累加
        List<SalaryTeam> indexList = sortSalaryTeam(salaries);

        Date afterSort = Times.now();
        System.out.println("sort and marge by first two word:" + (afterSort.getTime()-afterReadFile.getTime()) + "ms");

//        System.out.println(indexList.get(0).toString());
//        System.out.println(indexList.get(indexList.size()-1).toString());

        Collections.sort(indexList, new Comparator<SalaryTeam>() {
            public int compare(SalaryTeam o1, SalaryTeam o2) {
                return o1.getTotal() - o2.getTotal();
            }
        });

        if (indexList.size() > 10){
            for (int i = indexList.size()-1; i > indexList.size()-11; i--){
                String[] salaryArray = salaries.get(indexList.get(i).getFrom()).split(",");
                System.out.println(salaryArray[0].substring(0,2)+","+indexList.get(i).getTotal()+"万,"+(indexList.get(i).getTo()-indexList.get(i).getFrom()+1)+"人");
            }
        }

        Date getTenTop = Times.now();
        System.out.println("sort and get top ten:" + (getTenTop.getTime()-afterSort.getTime()) + "ms");

        System.out.println("total:" + (getTenTop.getTime()-timeBegin.getTime()) + "ms");
        
        Files.deleteFile(file);
    }

    private List<SalaryTeam> sortSalaryTeam(List<String> salaries){
        ForkJoinPool forkJoinPool = new ForkJoinPool(4);
        CountTask countTask = new CountTask(0,salaries.size()-1,salaries);
        Future<List<SalaryTeam>> result = forkJoinPool.submit(countTask);

        try {
            return result.get();
        } catch (InterruptedException e) {
            e.printStackTrace();
        } catch (ExecutionException e) {
            e.printStackTrace();
        }
        return null;
//        List<SalaryTeam> indexList = new LinkedList<>();
//        int from = 0;
//        for (int i = 0; i < salaries.size()-1; i++){
//            if(!compareFirstTwoWords(salaries.get(i),salaries.get(i+1))){
//                SalaryTeam salaryTeam = new SalaryTeam(from,i,calFromToTotal(from,i,salaries));
//                indexList.add(salaryTeam);
//                from = i+1;
//            }
//        }
//        //添加最后一个
//        SalaryTeam salaryTeam = new SalaryTeam(from,salaries.size()-1,calFromToTotal(from,salaries.size()-1,salaries));
//        indexList.add(salaryTeam);
//
//        return indexList;
    }

    private void writeFileUseFileWriter(File file){
        FileWriter fw = null;
        try {
            fw = new FileWriter(file,true);
            for (int i = 0; i < 10000000; i++){
                Salary salary = new Salary(generateSixChar(), (new Random().nextInt(10)+1),new Random().nextInt(50));
                fw.write(salary.toString()+"\n");
            }
        } catch (IOException var7) {
            throw Lang.wrapThrow(var7);
        } finally {
            if (fw != null){
                try {
                    fw.close();
                } catch (IOException e) {
                    e.printStackTrace();
                }
            }
        }
    }

    private List<String> readFile(File file){
        try {
            return java.nio.file.Files.readAllLines(file.toPath(),Encoding.CHARSET_UTF8);
        } catch (IOException e) {
            e.printStackTrace();
        }
        return null;
    }

    private static String generateSixChar(){
        String a = "abcdefghijklmnopqrstuvwxyz";
        char[] rands = new char[4];
        for (int i = 0; i < rands.length; i++)
        {
            int rand = (int) (Math.random() * a.length());
            rands[i] = a.charAt(rand);
        }
        return new String(rands);
    }
}
